using Godot;
using System.Collections.Generic;

[Tool]
public partial class ChromaPlatform : AnimatableBody2D
{
    // --- 移动设置 ---
    [ExportGroup("Movement")]
    [Export] public float MoveSpeed = 100.0f;
    [Export] public bool IsCyclic = true; // true=循环(A->B->C->A), false=往返(A->B->C->B->A)

    // --- 外观与颜色 ---
    [ExportGroup("Appearance")]
    [Export]
    public Vector2 Size
    {
        get => _size;
        set { _size = value; UpdateVisuals(); }
    }
    private Vector2 _size = new Vector2(96, 32);

    [Export]
    public BlockColor ColorType
    {
        get => _colorType;
        set { _colorType = value; UpdateVisuals(); }
    }
    private BlockColor _colorType = BlockColor.Red;

    // --- 内部引用 ---
    [Export] public Sprite2D VisualSprite;
    [Export] public CollisionShape2D Collider;
    [Export] public Line2D PathLine; // 用this定义路径

    // --- 运行时变量 ---
    private List<Vector2> _globalWaypoints = new List<Vector2>();
    private int _targetIndex = 0;
    private int _direction = 1; // 1 为正向, -1 为反向 (往返)
    private bool _isMoving = false;

    // Layer 常量
    private const int LAYER_WORLD = 1;
    private const int LAYER_RED = 2;
    private const int LAYER_BLUE = 3;
    private const int LAYER_GREEN = 4;

    public override void _Ready()
    {
        UpdateVisuals();

        if (!Engine.IsEditorHint())
        {
            InitializePath();
        }
    }

    private void InitializePath()
    {
        if (PathLine == null || PathLine.GetPointCount() < 2)
        {
            GD.PrintErr("ChromaPlatform: 路径点不足2个，无法移动！");
            return;
        }

        // 1. 先计算出所有的全局坐标点 (基于平台初始位置)
        // 这一步必须在修改 TopLevel 之前做！
        List<Vector2> globalPoints = new List<Vector2>();

        foreach (Vector2 point in PathLine.Points)
        {
            // ToGlobal 会把 Line2D 的局部坐标 (Local) 转换成 屏幕的世界坐标 (Global)
            // 比如点是 (0,0)，平台在 (100,100)，转换后就是 (100,100)
            globalPoints.Add(PathLine.ToGlobal(point));
        }

        // 把计算好的点存入用于移动逻辑的列表
        _globalWaypoints = new List<Vector2>(globalPoints);

        // 2. 将 Line2D 设为顶层节点 (视觉上与平台分离，不再随平台移动)
        PathLine.TopLevel = true;

        // 3. 【关键修正】重置 Line2D 的变换到世界原点
        // 因为我们接下来要直接把 Points 设为全局坐标，所以 Line2D 自身的原点必须是 (0,0)
        PathLine.GlobalPosition = Vector2.Zero;
        PathLine.GlobalRotation = 0;
        PathLine.Scale = Vector2.One;

        // 4. 将 Line2D 的点更新为全局坐标点
        PathLine.Points = globalPoints.ToArray();

        // 5. 初始化移动状态
        _isMoving = true;

        // 瞬移到第一个点开始 (通常第一个点就是 (0,0) 也就是当前位置，所以不会跳变)
        if (_globalWaypoints.Count > 0)
        {
            GlobalPosition = _globalWaypoints[0];
        }

        // 下一个目标是第1个点
        _targetIndex = 1;
    }

    public override void _PhysicsProcess(double delta)
    {
        if (Engine.IsEditorHint() || !_isMoving || _globalWaypoints.Count < 2) return;

        MovePlatform((float)delta);
    }

    private void MovePlatform(float dt)
    {
        Vector2 targetPos = _globalWaypoints[_targetIndex];
        Vector2 currentPos = GlobalPosition;

        // 1. 移动逻辑 (MoveToward)
        // AnimatableBody2D 不需要用 MoveAndSlide，直接改 GlobalPosition
        // 物理引擎会自动计算并推动站在上面的 CharacterBody2D
        Vector2 newPos = currentPos.MoveToward(targetPos, MoveSpeed * dt);
        GlobalPosition = newPos;

        // 2. 到达检测
        if (GlobalPosition.DistanceTo(targetPos) < 1.0f)
        {
            // 到达目标点，切换下一个点
            if (IsCyclic)
            {
                // 循环模式: 0 -> 1 -> 2 -> 0
                _targetIndex = (_targetIndex + 1) % _globalWaypoints.Count;
            }
            else
            {
                // 往返模式: 0 -> 1 -> 2 -> 1 -> 0
                _targetIndex += _direction;

                // 碰到头或尾就反向
                if (_targetIndex >= _globalWaypoints.Count - 1)
                {
                    _targetIndex = _globalWaypoints.Count - 1;
                    _direction = -1;
                }
                else if (_targetIndex <= 0)
                {
                    _targetIndex = 0;
                    _direction = 1;
                }
            }
        }
    }

    private void UpdateVisuals()
    {
        // 1. 形状与纹理
        if (VisualSprite != null)
            VisualSprite.RegionRect = new Rect2(Vector2.Zero, _size);
        if (Collider != null && Collider.Shape is RectangleShape2D rect)
            rect.Size = _size;

        // 2. 颜色与物理层 (Copy from ChromaBlock/Wall)
        SetCollisionLayerValue(LAYER_WORLD, false);
        SetCollisionLayerValue(LAYER_RED, false);
        SetCollisionLayerValue(LAYER_BLUE, false);

        SetCollisionLayerValue(LAYER_GREEN, false);

        switch (_colorType)
        {
            case BlockColor.Red:
                if (VisualSprite != null) VisualSprite.Modulate = Colors.Red;
                if (PathLine != null) PathLine.DefaultColor = new Color(1, 0, 0, 0.3f);
                SetCollisionLayerValue(LAYER_RED, true);
                break;

            case BlockColor.Blue:
                if (VisualSprite != null) VisualSprite.Modulate = Colors.Cyan;
                if (PathLine != null) PathLine.DefaultColor = new Color(0, 1, 1, 0.3f);
                SetCollisionLayerValue(LAYER_BLUE, true);
                break;


            case BlockColor.Green:
                if (VisualSprite != null) VisualSprite.Modulate = Colors.Lime;
                if (PathLine != null) PathLine.DefaultColor = new Color(0, 1, 0, 0.3f);
                SetCollisionLayerValue(LAYER_GREEN, true);
                break;

            case BlockColor.World:
                if (VisualSprite != null) VisualSprite.Modulate = Colors.White;
                if (PathLine != null) PathLine.DefaultColor = new Color(1, 1, 1, 0.3f);
                SetCollisionLayerValue(LAYER_WORLD, true);
                break;
        }




        UpdateSound();
    }


    [ExportGroup("Audio")]
    [Export] public AudioStreamPlayer2D HumSound;
    private void UpdateSound()
    {

        if (HumSound == null) return;
        if (Engine.IsEditorHint() || !IsInsideTree())
        {
            return;
        }

        float targetPitch = 1.0f;

        switch (ColorType)
        {
            case BlockColor.Red:
                targetPitch = Cfg.RedPitch;
                break;
            case BlockColor.Blue:
                targetPitch = Cfg.BluePitch;
                break;
            case BlockColor.Green:
                targetPitch = Cfg.GreenPitch;
                break;
            case BlockColor.World:
                targetPitch = 1.0f;
                break;
        }
        HumSound.PitchScale = targetPitch;
        // 2. 确保它在播放
        if (!HumSound.Playing && !Engine.IsEditorHint())
        {
            HumSound.Play();
        }
    }

}